// Barnes_Hut_Tree.cpp : Defines the entry point for the console application.
#include <GL/freeglut.h>
#include <pthread.h>
#include <stdlib.h>
#include <stdio.h>
#include <math.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/time.h>
#include <fcntl.h>
#include <unistd.h>
#include <assert.h>
#include "gen_struct.hpp"
#include "algorithm_bh.hpp"
#include "algorithm_bh.c"
#include "interface.c"
#include "glut_part.hpp"

/*=========================================================================*/ 
//TODO 
//fix "DestroyAll -> valgrind"
//make nice camera mode
void DataInit(char *DataList, gen_environ * gen_struct) 
{
	FILE * read_f;
	read_f = fopen(DataList, "r");
	if (read_f == NULL) {
		perror("Error: read Init Data Error\n");
		DestroyAll(gen_struct);
		exit(EXIT_FAILURE);
	}
	//TODO
	//data consistency is not guaranteed, check is required
	for (int i = 0; i < (gen_struct->nParticles); ++i) {
		assert(fscanf(read_f, "%lf", &(gen_struct->list[i].mass)));
		assert(fscanf(read_f, "%lf", &(gen_struct->list[i].position.x)));
		assert(fscanf(read_f, "%lf", &(gen_struct->list[i].position.y)));
		assert(fscanf(read_f, "%lf", &(gen_struct->list[i].position.z)));
		assert(fscanf(read_f, "%lf", &(gen_struct->list[i].vel.x)));
		assert(fscanf(read_f, "%lf", &(gen_struct->list[i].vel.y)));
		assert(fscanf(read_f, "%lf", &(gen_struct->list[i].vel.z)));
	}
	fclose(read_f);
}


/*=========================================================================*/
int main(int argc, char *argv[])
{
	if (argc < 3) {
		printf
		    ("Usage filename["%s"], count of particles["%d"]\n");
		return 0;
	}
	int i = atoi(argv[2]);	//number of particles
	//glut part.hpp contains gen_info
	InitGenInfo(&gen_info, i);
	DataInit(argv[1], gen_info); 
	glutInit(&argc, argv);
	GLInit();
	glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH);
	glutInitWindowSize(WinWidth, WinHeight);
	glutInitWindowPosition((glutGet(GLUT_SCREEN_WIDTH) -
				 WinWidth) / 2,
				(glutGet(GLUT_SCREEN_HEIGHT) -
				 WinHeight) / 2);
	glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
	gen_info->GLwd = glutCreateWindow("GrSimulation_v0.0:Stopped");
	glutDisplayFunc(Display);
	glutKeyboardFunc(Keyboard);
	glutReshapeFunc(Reshape);
	glutMouseFunc(Mouse);
	glutMotionFunc(MouseMotion);
	//TODO
	//use glutDestroyWindow, glutLeaveMainLoop
	glutMainLoop();
	return 0;
}

